package hoang.hut.app.map;

import java.util.ArrayList;
import java.util.List;

import org.json.JSONArray;
import org.json.JSONObject;

import android.content.Context;
import android.graphics.Bitmap;
import android.location.Address;
import android.location.Geocoder;

import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
import com.google.android.gms.maps.model.PolylineOptions;

public class MapDrawing {
	public static double Radius = 6371; // radius of earth
	/*Context mContext;
	
	public MapDrawing(Context mContext) {
		super();
		this.mContext = mContext;
	}*/
	/**
	 * tao url request google server
	 * 
	 * @param sourceAddress: dia chi nguon
	 * @param destAddress: dia chi dich
	 * @return: file json
	 */
	public static String makeURL(String sourceAddress, String destAddress) {
		StringBuilder urlString = new StringBuilder();
		urlString.append("http://maps.googleapis.com/maps/api/directions/json");
		urlString.append("?origin=");
		urlString.append(sourceAddress);
		urlString.append("&destination=");
		urlString.append(destAddress);
		urlString.append("&sensor=false&mode=driving&alternatives=true");
		return urlString.toString();
	}
	/**
	 * tao url request google server
	 * 
	 * @param sourcelat: lat 
	 * @param sourcelog: lon 
	 * @param destlat: lat
	 * @param destlog: lon 
	 * @return: fie json
	 */
	public static String makeURL(double sourcelat, double sourcelog, double destlat,
			double destlog) {
		StringBuilder urlString = new StringBuilder();
		urlString.append("http://maps.googleapis.com/maps/api/directions/json");
		urlString.append("?origin=");
		urlString.append(Double.toString(sourcelat));
		urlString.append(",");
		urlString.append(Double.toString(sourcelog));
		urlString.append("&destination=");
		urlString.append(Double.toString(destlat));
		urlString.append(",");
		urlString.append(Double.toString(destlog));
		urlString.append("&sensor=false&mode=driving&alternatives=true");
		return urlString.toString();
	}
	/*
	 * ve duong thang noi 2 diem
	 */
	public static void drawLine(GoogleMap googleMap, LatLng src, LatLng des,
			int color, int width) {
		googleMap.addPolyline(new PolylineOptions().add(src).add(des)
				.color(color).width(width));
	}
	/**
	 * ve duong theo danh sach cac diem
	 * 
	 * @param googleMap
	 * @param listPoint
	 * @param color
	 * @param width
	 */
	public static void drawPath(Context mContext,GoogleMap googleMap, List<LatLng> listPoint,
			int color, int width) {

		for (int i = 0; i < listPoint.size() - 1; i++) {
			LatLng src = listPoint.get(i);
			LatLng des = listPoint.get(i + 1);
			drawLine(googleMap, src, des, color, width);
		}

	}
	/**
	 * ve duong di tu google
	 * 
	 * @param googleMap
	 * @param json: file json google tra ve
	 * @param color: mÃ u váº½
	 * @param width: Ä‘á»™ rá»™ng 
	 */
	public static void drawPath(Context mContext, GoogleMap googleMap, String json, int color, int width) {
		try {
			JSONObject jsonObject = new JSONObject(json);
			JSONArray routes = jsonObject.getJSONArray("routes");
			JSONObject jsonObject2 = routes.getJSONObject(0);

			JSONObject jsonPolyline = jsonObject2
					.getJSONObject("overview_polyline");
			String encodePolyline = jsonPolyline.getString("points");

			List<LatLng> listPoint = decodePoly(encodePolyline);

			for (int i = 0; i < listPoint.size() - 1; i++) {
				LatLng src = listPoint.get(i);
				LatLng des = listPoint.get(i + 1);

				drawLine(googleMap, src, des, color, width);
				//addMarker(mContext, googleMap, src.latitude, src.longitude, listPoint.get(i)., icon)
			}
		} catch (Exception e) {
		}
	}
	/**
	 * danh dau 1 diem tren ban do
	 * 
	 * @param mContext
	 * @param googleMap
	 * @param lat
	 * @param lon
	 * @param title
	 * @param icon: anh Bitmap
	 */
	public static void addMarker(Context mContext, GoogleMap googleMap, double lat, double lon, String title, Bitmap icon){
		googleMap.addMarker(new MarkerOptions().position(new LatLng(lat, lon))
				.title(title)
				.snippet(getAddress(mContext, lat, lon))
				.icon(BitmapDescriptorFactory.fromBitmap(icon)));
	}
	/**
	 * danh dau 1 diem tren ban do
	 * 
	 * @param mContext
	 * @param googleMap
	 * @param lat
	 * @param lon
	 * @param title
	 * @param icon: anh default: BitmapDescriptorFactory.HUE_BLUE
	 */
	public static void addMarker(Context mContext, GoogleMap googleMap, double lat, double lon, String title, float icon){
		googleMap.addMarker(new MarkerOptions().position(new LatLng(lat, lon))
				.title(title)
				.snippet(getAddress(mContext, lat, lon))
				.icon(BitmapDescriptorFactory.defaultMarker(icon)));
	}
	/**
	 * lay danh sach point tu viec giai ma json
	 * 
	 * @param encoded
	 * @return
	 */
	public static List<LatLng> decodePoly(String encoded) {
		List<LatLng> poly = new ArrayList<LatLng>();
		int index = 0;
		int len = encoded.length();
		int lat = 0;
		int lng = 0;

		while (index < len) {
			int shift = 0;
			int result = 0;
			int b;
			do {
				b = encoded.charAt(index++) - '?';
				result |= (b & 0x1F) << shift;
				shift += 5;
			} while (b >= 32);
			int dlat = (result & 0x1) != 0 ? result >> 1 ^ 0xFFFFFFFF
					: result >> 1;
			lat += dlat;

			shift = 0;
			result = 0;
			do {
				b = encoded.charAt(index++) - '?';
				result |= (b & 0x1F) << shift;
				shift += 5;
			} while (b >= 32);
			int dlng = (result & 0x1) != 0 ? result >> 1 ^ 0xFFFFFFFF
					: result >> 1;
			lng += dlng;

			LatLng p = new LatLng(lat / 100000.0D, lng / 100000.0D);
			poly.add(p);
		}
		return poly;
	}
	/**
	 * lay dia chi thuc cua 1 diem tren ban do
	 * 
	 * @param mContext
	 * @param lat: 
	 * @param lon:
	 * @return 
	 */
	public static String getAddress(Context mContext, double lat, double lon){
		String add = "";
		List<Address> arrayAddress = null;
		Geocoder geocoder = new Geocoder(mContext);
		try {
			arrayAddress = geocoder.getFromLocation(lat, lon, 1);
		} catch (Exception e) {
		}

		if (arrayAddress == null || arrayAddress.size() == 0) {
			return add;
		} else {
            for (int j=0; j<arrayAddress.get(0).getMaxAddressLineIndex(); j++){
            	 add += arrayAddress.get(0).getAddressLine(j) + ", ";
            }
		}
		return add;
	}
	/**
	 * tinh khoang cach giua 2 point tren ban do
	 * 
	 * @param lat
	 * @param lon
	 * @param lat3
	 * @param lon2
	 * @return
	 */
	public static double calculateDistanCe(double lat, double lon, double lat3,
			double lon2) {
		double dLat, dLon, latitude1 = lat, latitude2 = lat3, longitude2 = lon2, longitude1 = lon, lat1, lat2, c, a;
		// degree to radian
		dLat = deg2rad(latitude2 - latitude1);
		dLon = deg2rad(longitude2 - longitude1);
		lat1 = deg2rad(latitude1);
		lat2 = deg2rad(latitude2);

		a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.sin(dLon / 2)
				* Math.sin(dLon / 2) * Math.cos(lat1) * Math.cos(lat2);
		c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
		return Radius * c;
	}


	private static double deg2rad(double deg) {
		return (deg * Math.PI / 180.0);
	}
	
		
	
}
